package ys.ewp.dao;

import java.lang.reflect.ParameterizedType;
import java.sql.SQLException;
import java.util.LinkedHashMap;
import java.util.List;

import javax.annotation.Resource;

import org.hibernate.HibernateException;
import org.hibernate.Query;
import org.hibernate.Session;
import org.springframework.orm.hibernate3.HibernateCallback;
import org.springframework.orm.hibernate3.HibernateTemplate;

@SuppressWarnings("unchecked")
public abstract class BaseDao<T> {
	
	private Class<T> entityClass;
	
	public BaseDao() {
		entityClass =(Class<T>) ((ParameterizedType) getClass().getGenericSuperclass()).getActualTypeArguments()[0];
	}
	
	private HibernateTemplate hibernateTemplate;

	@Resource
	public void setHibernateTemplate(HibernateTemplate hibernateTemplate) {
		this.hibernateTemplate = hibernateTemplate;
	}
	
	/**
	 *@功能  清除一级缓存的数据
	 */
	public void clear(){
		this.hibernateTemplate.clear();
	}
	
	/**
	 *@功能  获取实体
	 */
	public T get(Class<T> clazz, Integer id) {
		return (T) this.hibernateTemplate.get(clazz, id);
	}
	
	/**
	 *@功能  获取实体
	 */
	public T get(Integer id){
		T clazz = (T) this.get(entityClass, id);
		return clazz;
	}
	
	/**
	 *@功能  保存实体
	 */
	public void save(T clazz) {
		this.hibernateTemplate.save(clazz);
	}
	
	/**
	 *@功能  更新实体
	 */
	public void update(T clazz) {
		this.hibernateTemplate.update(clazz);
	}
	
	/**
	 *@功能  删除实体
	 */
	public void delete(T clazz) {
		this.hibernateTemplate.delete(clazz);
	}
	
	/**
	 *@功能  删除实体
	 */
	public void delete(Integer id){
		T clazz = (T) this.hibernateTemplate.get(entityClass, id);
		this.delete(clazz);
	}
	
	/**
	 *@功能  获取记录总数
	 */
	public Long getCount(){
		return getCount(null, null);
	}
	
	/**
	 *@功能  获取记录总数
	 */
	public Long getCount(String where,Object[] params){
		String hql="select count(o) from "+this.getEntityName()+" o "+(where==null || "".equals(where.trim())? "": "where "+ where);
		return (Long)hibernateTemplate.find(hql,params).get(0);
	}

	
	/**
	 * @功能 获得指定数量对象
	 */
	public List<T> getListByNum(final Integer num){	
		return getListByNum(num,null,null,null);
	}
	/**
	 * @功能 获得指定数量对象
	 */
	public List<T> getListByNum(final Integer num,LinkedHashMap<String, String> orderby){	
		return getListByNum(num,null,null,orderby);
	}
	/**
	 * @功能 获得指定数量 对象
	 */
	public List<T> getListByNum(final Integer num,final String where,final Object[] params){	
		return getListByNum(num,where,params,null);
	}
	/**
	 *@功能  获取指定数量的对象
	 */
	public List<T> getListByNum(final Integer num, final String where, final Object[] params, LinkedHashMap<String, String> orderby){	
		final String hql="from "+this.getEntityName()+" o "+(where==null || "".equals(where.trim())? "": "where "+ where)+ buildOrderby(orderby);
		
		List<T> list = this.hibernateTemplate.executeFind(
			new HibernateCallback() {
				public Object doInHibernate(Session session) throws HibernateException, SQLException {
					Query query=session.createQuery(hql);
					setQueryParams(query, params);
					return query.setMaxResults(num).list(); 
				}
			});
		return list;
	}
	
	/**
	 * @功能 获得所有对象
	 */
	public List<T> getList(){
		return getPageList(-1,-1,null,null,null);
	}
	
	/**
	 * @功能 获得所有对象
	 */
	public List<T> getList(LinkedHashMap<String, String> orderby){
		return getPageList(-1,-1,null,null,orderby);
	}
	
	/**
	 * @功能 获得所有对象
	 */
	public List<T> getList(String where,Object[] params){	
		return getPageList(-1,-1,where,params,null);
	}
	
	/**
	 * @功能 获得所有对象
	 */
	public List<T> getList(String where, Object[] params, LinkedHashMap<String, String> orderby){	
		return getPageList(-1,-1,where,params,orderby);
	}
	
	
	
	/**
	 * @功能 获得分页结果集
	 */
	public List<T> getPageList(final Integer firstResult, final Integer maxResults, final String where, final Object[] params, LinkedHashMap<String, String> orderby) {
		//原始语句
		final String hql="from "+this.getEntityName()+" o "+(where==null || "".equals(where.trim())? "": "where "+ where)+ buildOrderby(orderby);
		
		List<T> list = this.hibernateTemplate.executeFind(
				new HibernateCallback() {
					public Object doInHibernate(Session session) throws HibernateException, SQLException {
						Query query=session.createQuery(hql);
						setQueryParams(query, params);
						//判断是否分页查询
						if(firstResult!=-1 && maxResults!=-1){
							query.setFirstResult(firstResult).setMaxResults(maxResults);
						}
						return query.list();
					}
				});
		return list;
	}
	
	/**
	 *@功能  获取实体名称
	 */
	private String getEntityName() {
		return entityClass.getSimpleName();
	}
	
	/**
	 *@功能  拼装查询参数
	 */
	private void setQueryParams(Query query, Object[] params){
		if(params!=null && params.length>0){
			for(int i=0; i<params.length; i++){
				query.setParameter(i, params[i]);
			}
		}
	}
	
	/**
	 *@功能  组装order by语句
	 */
	private String buildOrderby(LinkedHashMap<String, String> orderby){
		StringBuffer orderByQl = new StringBuffer("");
		if(orderby!=null && orderby.size()>0){
			orderByQl.append(" order by ");
			for(String key : orderby.keySet()){
				orderByQl.append("o.").append(key).append(" ").append(orderby.get(key)).append(",");
			}
			orderByQl.deleteCharAt(orderByQl.length()-1);
		}
		return orderByQl.toString();
	}
	
}
